package com.rrjjg.app.admin.bus;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.netflix.appinfo.InstanceInfo;
import com.rrjjg.app.admin.data.service.IPropertiesHistoryService;
import com.rrjjg.app.admin.data.service.IPropertiesService;
import com.rrjjg.app.admin.data.storage.entity.Properties;
import com.rrjjg.app.admin.data.storage.entity.PropertiesHistory;
import com.rrjjg.app.admin.module.enums.EurekaStatus;
import com.rrjjg.app.mybatis.bean.PageData;
import com.rrjjg.app.mybatis.util.PageUtil;
import lombok.val;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cloud.client.ServiceInstance;
import org.springframework.cloud.client.discovery.DiscoveryClient;
import org.springframework.cloud.netflix.eureka.EurekaServiceInstance;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpMethod;
import org.springframework.http.MediaType;
import org.springframework.stereotype.Component;
import org.springframework.util.CollectionUtils;
import org.springframework.web.client.RestTemplate;

import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;

import static com.rrjjg.app.admin.module.Constants.*;
import static com.rrjjg.app.admin.module.EurekaApi.*;

/**
 * ----------------------------------------------------------------------------- <br>
 * 功能 :  <br>
 * ----------------------------------------------------------------------------- <br>
 * 作者 : Vayne <br>
 * 时间 : 2023/4/18 <br>
 */
@Component
public class BPropertiesService {

    @Autowired
    IPropertiesService iPropertiesService;
    @Autowired
    IPropertiesHistoryService iPropertiesHistoryService;
    @Autowired
    DiscoveryClient discoveryClient;
    @Autowired
    RestTemplate restTemplate;
    @Value("${eureka.client.service-url.defaultZone}")
    private String eurekaUrl;



    public PageData<Properties> queryPage(Properties properties, int  page, int size){
        QueryWrapper wrapper = PageUtil.queryWrapper(properties, Properties.class);
        Page ans = iPropertiesService.page(new Page(page, size), wrapper);
        return PageUtil.EtoVList(ans );
    }

    public PageData<Properties> queryPageh(PropertiesHistory properties, int  page, int size){
        QueryWrapper wrapper = PageUtil.queryWrapper(properties, PropertiesHistory.class);
        Page ans = iPropertiesHistoryService.page(new Page(page, size), wrapper);
        return PageUtil.EtoVList(ans );
    }


    public List<String> push(String application, List<String> list) {
        List<ServiceInstance> instances = discoveryClient.getInstances(application);
        List<String> ans = new ArrayList<>();
        for (ServiceInstance instance : instances) {
            EurekaServiceInstance esi = (EurekaServiceInstance) instance;
            InstanceInfo instanceInfo = esi.getInstanceInfo();
            String ipAddr = instanceInfo.getIPAddr();
            if (list.contains(ipAddr)) {
                ans.addAll(restTemplate.postForObject(HTTP + ipAddr + COLON + instanceInfo.getPort() + REFRESH, "{}", List.class));
            }
        }
        return ans;
    }


    public List<String> eurekaSerive(String application){
        val instances = discoveryClient.getInstances(application);
        List<String> ans = new ArrayList<>();
        if(!CollectionUtils.isEmpty(instances)){
            for (ServiceInstance instance : instances) {
                EurekaServiceInstance esi = (EurekaServiceInstance) instance;
                ans.add(esi.getHost());
            }
        }
        return ans;
    }

    public void upOrDown(String application,Integer type,List<String> list) {
        val split = eurekaUrl.split(COMMA);
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_XML);
        HttpEntity httpEntity = new HttpEntity(null, headers);
        val exchange = restTemplate.exchange(split[0] + APPS, HttpMethod.GET, httpEntity, JSONObject.class);
        val appsDto = exchange.getBody();
        JSONObject applications = appsDto.getJSONObject(APP_S);
        JSONArray apps= applications.getJSONArray(APP_O);
        String[] eUrl = eurekaUrl.split(COMMA);
        for (Object app : apps) {
            LinkedHashMap<String,Object> jo  = (LinkedHashMap<String,Object>) app;
            val appid = jo.get(APP_ID);
            if(!application.equals(appid)){
                continue;
            }
            List<Object> instance = (ArrayList) jo.get(INSTANCE_S);
            for (Object o : instance) {
                LinkedHashMap<String,Object> insts  = (LinkedHashMap<String,Object>) o;
                val ip = insts.get(IP);
                if(!list.contains(ip)){
                    continue;
                }
                val status = insts.get(STATUS_ID);
                val val = EurekaStatus.getByCode(type).getVal();
                if(val.equals(status)){
                    return;
                }
                val instanceId = insts.get(INSTANCE_ID);
                restTemplate.put(eUrl[0]+APPS+SLASH+appid+SLASH+instanceId+STATUS+val,null);
            }
        }
    }


    public IPropertiesService getiPropertiesService() {
        return iPropertiesService;
    }

    public IPropertiesHistoryService getiPropertiesHistoryService() {
        return iPropertiesHistoryService;
    }
}
